//-------------------------------------------------------------------
//	Copyright (c) 2010-2012 Zhirnov Andrey
//	This file is part of the "UXGEN" project.
//	See copyright notice in "Engine.h".
//-------------------------------------------------------------------

#ifndef _UX_RT_PASSMANAGER_H
#define _UX_RT_PASSMANAGER_H

#include "Passes/IRTPass.h"
#include "Passes/Builtin.h"
#include "Passes/Custom.h"
#include "ConfiguredRTTypes.h"
#include "LightTech/ILightTechnique.h"

namespace Engine
{
namespace RenderUtils
{

	//
	// Render Technique Pass Manager
	//

	class _EXPORT_ CRTPassManager : public CEngBaseObject
	{
	public:
		typedef pod_array< IRTPass *>	rt_pass_array_t;

		struct TRenderTargetInfo
		{
			CTexturePtr		pTexture;
			string			sName;
			///
			TRenderTargetInfo() {}
			TRenderTargetInfo(const CTexturePtr &tex, const string &name): pTexture(tex), sName(name) {}
		};

		struct TPassName
		{
			const string		*	pName;
			usize					uIndex;
			IRTPass::EPassType	eType;
			///
			TPassName(): pName(nullptr), uIndex(-1), eType(IRTPass::UNKNOWN) {}
			TPassName(const string &name, usize idx, IRTPass::EPassType type): pName(&name), uIndex(idx), eType(type) {}
		};

		struct TTechParams
		{
			const TConfiguredRTInit &	sInit;
			array< TRenderTargetInfo >	aRenderTargets;
			array< TPassName >			aPassCache;
			bool						bProfiling;
			bool						bForwardRender;
			///
			TTechParams(const TConfiguredRTInit &init): sInit(init), bProfiling(false), bForwardRender(false) {}
		};

		typedef bool (*PCreateBuiltinPassProc_t)(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		

	protected:
		struct _TBuiltin
		{
			PCreateBuiltinPassProc_t	pProc;
			string						sName;
			///
			_TBuiltin(): pProc(nullptr) {}
			_TBuiltin(PCreateBuiltinPassProc_t proc, const string &name): pProc(proc), sName(name) {}
		};

	protected:
		array< _TBuiltin >	_aBuiltinPasses;
		
	protected:
		bool _ProcessConsole(const string_array_t &aConsole, TTechParams &sTech);
		bool _CreatePasses(rt_pass_array_t &aPasses, TTechParams &sTech);
		bool _CreateRenderTarget(const TRenderTarget &sRT, TTechParams &sTech);
		bool _CreatePass(const string &sName, IRTPass *&pPass, IRTPass *pParent, const TTechParams &sTech);
		
		static bool _s_CreateUseUserPostProcessPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateDrawFullscreenQuadPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateDrawRenderQueueOCPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateDrawRenderQueuePass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateProfilerBeginPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateProfilerEndPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateClearBufferPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateSetupShadowPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateSetupLightPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateDrawLightsPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		static bool _s_CreateSetCameraPass(IRTPass *&, const string_array_t &, IRTPass *, const TTechParams &);
		
		bool _CreateCyclePass(IRTPass *&, IRTPass *, const TRTCyclePass &, const TTechParams &);
		bool _CreateCustomPass(IRTPass *&, IRTPass *, const TRTCustomPass &, const TTechParams &);
		bool _CreateBranchPass(IRTPass *&, IRTPass *, const TRTBranchPass &, const TTechParams &);
		bool _CreateSwizzlePass(IRTPass *&, IRTPass *, const TRTSwizzlePass &, const TTechParams &);
		bool _CreateSetStatesPass(IRTPass *&, IRTPass *, const TRTSetGLStatesPass &, const TTechParams &);
		bool _CreatePostProcessPass(IRTPass *&, IRTPass *, const TRTPostProcessPass &, const TTechParams &);
		bool _CreateBindTexturesPass(IRTPass *&, IRTPass *, const TRTBindTexturesPass &, const TTechParams &);
		bool _CreateSetRenderTargetsPass(IRTPass *&, IRTPass *, const TRTSetRenderTargetsPass &, const TTechParams &);

		// CEngBaseObject //
		virtual void Release();

	public:
		CRTPassManager();
		~CRTPassManager();

		bool CreatePasses(const TConfiguredRTInit &sInit, rt_pass_array_t &aPasses);

		bool RegisterBuiltinPass(const string &sName, PCreateBuiltinPassProc_t pProc);
		bool UnregisterBuiltinPass(const string &sName);

		bool RegisterLightTechnique(ILightTechnique *);
		bool UnregisterLightTechnique(ILightTechnique *);
	};

//-------------------------------------------------------------------

}	// RenderUtils
}	// Engine

#endif	// _UX_RT_PASSMANAGER_H